package com.noble.meether.chat.ui.agora.util;

import android.content.Context;
import android.content.res.AssetFileDescriptor;
import android.content.res.AssetManager;
import android.graphics.Bitmap;
import android.media.MediaPlayer;
import android.media.RingtoneManager;
import android.net.Uri;
import android.os.Handler;
import android.os.Looper;
import android.os.Message;
import android.os.Vibrator;
import android.view.View;
import android.view.ViewGroup;

import com.noble.glamour.module.logic.application.App;
import com.noble.glamour.module.logic.application.ModuleMgr;
import com.noble.glamour.module.logic.request.RequestComplete;
import com.noble.library.dir.DirType;
import com.noble.library.log.PToast;
import com.noble.library.observe.MsgMgr;
import com.noble.library.utils.BitmapUtil;
import com.noble.library.utils.FileUtil;
import com.noble.meether.R;
import com.noble.meether.chat.ui.agora.act.bean.ChatStatus;
import com.noble.meether.chat.ui.agora.model.AgoraConstant;
import com.noble.meether.chat.ui.agora.model.EngineConfig;
import com.noble.meether.logic.media.MediaConstant;
import com.noble.meether.logic.third.screenshot.InstaCapture;
import com.tarek360.instacapture.listener.ScreenCaptureListener;
import com.trello.rxlifecycle2.components.support.RxAppCompatActivity;

import java.io.IOException;

/**
 * 轮询心跳辅助类
 * Created by Su on 2017/4/13.
 */
public class RtcSubUtil implements Handler.Callback {
    private volatile static RtcSubUtil mInstance;

    private RtcSubUtil() {
        initHandler();
    }

    public static RtcSubUtil getInstance() {
        if (mInstance == null) {
            synchronized (RtcSubUtil.class) {
                if (mInstance == null) {
                    mInstance = new RtcSubUtil();
                }
            }
        }
        return mInstance;
    }

    // ==================== 付费轮询 =================================

    /**
     * 开启付费轮询
     */
    public void startVideoChatTime() {
        stopVideoChatTime();
        if (videoChatHandler == null) {
            initHandler();
        }
        videoChatHandler.sendEmptyMessageDelayed(LOCATION_EVENT_START, AgoraConstant.CHAT_UPDATE_PAY_INFO);
    }

    /**
     * 关闭付费轮询
     */
    public void stopVideoChatTime() {
        if (videoChatHandler != null) {
            videoChatHandler.removeMessages(LOCATION_EVENT_START);
        }
    }

    /**
     * 短付费轮询间隔
     */
    public void startTinyVideoChatTime() {
        reqCheckVideoChat();
        stopTinyVideoChatTime();
        if (videoChatHandler == null) {
            initHandler();
        }
        videoChatHandler.sendEmptyMessageDelayed(LOCATION_EVENT_TINY_START, AgoraConstant.CHAT_UPDATE_PAY_FAIL);
    }

    /**
     * 关闭短付费轮询
     */
    public void stopTinyVideoChatTime() {
        if (videoChatHandler != null) {
            videoChatHandler.removeMessages(LOCATION_EVENT_TINY_START);
        }
    }

    // ==================== 鉴黄轮询 =================================
    private boolean isFirstUpload = true; // 是否是首个一分钟内上传鉴黄图片
    private long intervalFirshTime = 0;   // 在线配置接通一分钟内上传时间间隔
    private long intervalTime = 0;        // 在线配置接通一分钟后上传时间间隔

    /**
     * 设置配置信息： 开启鉴黄轮询前调用该方法
     */
    public void setIntervalConfig(long intervalFirshTime, long intervalTime) {
        this.intervalFirshTime = intervalFirshTime;
        this.intervalTime = intervalTime;
    }

    /**
     * 设置变更轮询间隔： 通信一分钟时调用
     */
    public void resetFirstUpload() {
        isFirstUpload = false;
    }

    /**
     * 鉴黄图片上传轮询
     */
    public void startPicTime() {
        stopPicTime();
        if (picHandler == null)
            initPicHandler();

        if (isFirstUpload) {
            picHandler.sendEmptyMessageDelayed(LOCATION_UPLOAD_START,
                    intervalFirshTime <= 0 ? AgoraConstant.CHAT_UPDATE_VIDEO_PIC_FIRST : intervalFirshTime);
            return;
        }
        picHandler.sendEmptyMessageDelayed(LOCATION_UPLOAD_START,
                intervalTime <= 0 ? AgoraConstant.CHAT_UPDATE_VIDEO_PIC : intervalTime);
    }

    /**
     * 关闭鉴黄轮询
     */
    public void stopPicTime() {
        if (picHandler != null)
            picHandler.removeMessages(LOCATION_UPLOAD_START);
    }

    // ====================================================
    private static final int LOCATION_EVENT_START = 0;
    private static final int LOCATION_UPLOAD_START = 1;
    private static final int LOCATION_EVENT_TINY_START = 2;
    private Handler videoChatHandler = null; // 付费轮询控制器
    private Handler picHandler = null;       // 图片轮询上传控制器


    private void initHandler() {
        Looper looper;
        if ((looper = Looper.myLooper()) != null) {
            videoChatHandler = new Handler(looper, this);
        } else if ((looper = Looper.getMainLooper()) != null) {
            videoChatHandler = new Handler(looper, this);
        } else {
            videoChatHandler = null;
        }
    }

    private void initPicHandler() {
        Looper looper;
        if ((looper = Looper.myLooper()) != null) {
            picHandler = new Handler(looper, this);
        } else if ((looper = Looper.getMainLooper()) != null) {
            picHandler = new Handler(looper, this);
        } else {
            picHandler = null;
        }
    }

    @Override
    public boolean handleMessage(Message msg) {
        switch (msg.what) {
            case LOCATION_EVENT_START:
                startVideoChatTime();
                reqCheckVideoChat();
                break;

            case LOCATION_EVENT_TINY_START:
                startTinyVideoChatTime();
                break;

            case LOCATION_UPLOAD_START:
                startPicTime();
                saveScreenShoot();
                break;
        }
        return false;
    }

    // ==========================================  付费轮询回调  =====================================
    private boolean isTinyBeated = false;  // 是否进行过付费短轮询
    private int tinyVideoBeatTimes = 1;    // 付费请求失败后，短轮询间隔请求次数

    private EngineConfig config() {
        return ModuleMgr.getRtcEnginMgr().getEngineConfig();
    }

    /**
     * 一进入通话5s后进行检测， 查看start接口是否调用成功
     * 单纯做判断使用
     */
    public void reqCheckStart(RxAppCompatActivity activity) {
        if (!ModuleMgr.getCenterMgr().getMyInfo().isMan()) return;
        MsgMgr.getInstance().delay(activity, () -> ModuleMgr.getRtcChatMgr().reqCheckVideoChat(config().mVcid, response -> {
            if (!response.isOk()) {
                RtcJointChannel.getInstance().reqChatStart();
                return;
            }
            ChatStatus chatStatus = (ChatStatus) response.getBaseData();
            ModuleMgr.getCenterMgr().getMyInfo().setDiamand(chatStatus.getDoLeave()); // 更新本地钻石
            showCountView(chatStatus.getSecondLeave());
        }), 5000);
    }

    /**
     * 轮询付费信息
     */
    private void reqCheckVideoChat() {
        ModuleMgr.getRtcChatMgr().reqCheckVideoChat(config().mVcid, response -> {
            if (response.isOk()) {
                ChatStatus chatStatus = (ChatStatus) response.getBaseData();
                ModuleMgr.getCenterMgr().getMyInfo().setDiamand(chatStatus.getDoLeave()); // 更新本地钻石

                // 倒计时统计
                showCountView(chatStatus.getSecondLeave());
                if (isTinyBeated) {
                    isTinyBeated = false;
                    tinyVideoBeatTimes = 1;
                    stopTinyVideoChatTime();  // 关闭短轮询
                    startVideoChatTime();     // 开启长轮询
                }
                return;
            }
            startTinyTime();
        });
    }

    /**
     * 展示倒计时逻辑
     */
    public void showCountView(long secLeave) {
        if (secLeave <= AgoraConstant.CHAT_COST_PROMPT) {    // 开启倒计时
            RtcTimerUtil.getInstance().startStatisTipsTime(secLeave * 1000);
        }
    }

    /**
     * 短付费轮询间隔
     */
    private void startTinyTime() {
        isTinyBeated = true;

        // 超过5次未请求成功，挂断通信
        if (tinyVideoBeatTimes == AgoraConstant.CHAT_UPDATE_PAY_FAIL_TIME) {
            PToast.showShort(App.activity.getString(R.string.chat_pay_info_fail));
            RtcJointChannel.getInstance().stopChat();
            return;
        }

        // 只在第一次时开启短轮询
        if (tinyVideoBeatTimes == 1) {
            startTinyVideoChatTime();
        }
        ++tinyVideoBeatTimes;
    }


    // ==========================  鉴黄轮询回调  =============
    private View captureView = null;        // 需要截取的View

    public void setCaptureView(View captureView) {
        this.captureView = captureView;
    }

    private void saveScreenShoot() {
        if (captureView == null) return;

        new Thread(() -> InstaCapture.getInstance(App.activity).capture(captureView).setScreenCapturingListener(new ScreenCaptureListener() {
            @Override
            public void onCaptureStarted() {
            }

            @Override
            public void onCaptureFailed(Throwable e) {
            }

            @Override
            public void onCaptureComplete(Bitmap bitmap) {
                final String saveBitmap = BitmapUtil.saveBitmap(bitmap, DirType.getUploadDir() + System.currentTimeMillis() + ".jpg");
                ModuleMgr.getMediaMgr().sendCheckPorno(config().mVcid, saveBitmap, AgoraConstant.PIC_TYPE_VIDEO_CHAT, null);
            }
        })).start();
    }


    public void release() {
        if (captureView != null && captureView.getParent() != null) {
            ((ViewGroup) captureView.getParent()).removeView(captureView);
            captureView = null;
        }
    }

    // ======================= 举报截图 ===========================
    public void saveReportShoot(RequestComplete complete) {
        if (captureView == null) return;

        new Thread(() -> InstaCapture.getInstance(App.activity).capture(captureView).setScreenCapturingListener(new ScreenCaptureListener() {
            @Override
            public void onCaptureStarted() {
            }

            @Override
            public void onCaptureFailed(Throwable e) {
            }

            @Override
            public void onCaptureComplete(Bitmap bitmap) {
                final String saveBitmap = BitmapUtil.saveBitmap(bitmap, DirType.getUploadDir() + System.currentTimeMillis() + ".jpg");
                ModuleMgr.getMediaMgr().sendHttpFile(MediaConstant.UPLOAD_REPORT, saveBitmap, response -> {
                    if (complete != null)
                        complete.onRequestComplete(response);
                    FileUtil.deleteFile(saveBitmap);
                });
            }
        })).start();
    }


    // ======================= 铃声播放 ===========================
    private MediaPlayer mMediaPlayer;   // 铃声
    private Vibrator vibrator;          // 振动

    /**
     * 开启铃声
     */
    public void playSound() {
        try {
            AssetManager assetManager = App.context.getAssets();
            AssetFileDescriptor afd = assetManager.openFd("ring.mp3");
            mMediaPlayer = new MediaPlayer();
            mMediaPlayer.setDataSource(afd.getFileDescriptor(),
                    afd.getStartOffset(), afd.getLength());
            mMediaPlayer.setLooping(true);
            mMediaPlayer.prepare();
            mMediaPlayer.start();
        } catch (IOException e) {
            e.printStackTrace();
        }
    }

    public void stopPlay() {
        if (mMediaPlayer != null)
            mMediaPlayer.stop();
        mMediaPlayer = null;
    }

    /**
     * 震动
     */
    public void vibrator() {
        vibrator = (Vibrator) App.context.getSystemService(Context.VIBRATOR_SERVICE);
        long[] pattern = {600, 800};
        vibrator.vibrate(pattern, 0);
    }

    public void stopVibrator() {
        if (vibrator != null)
            vibrator.cancel();
        vibrator = null;
    }

    /**
     * 获取系统默认铃声的Uri
     */
    private Uri getSystemDefultRingtoneUri() {
        return RingtoneManager.getActualDefaultRingtoneUri(App.context,
                RingtoneManager.TYPE_RINGTONE);
    }

}
